use crate::unsafe_assign;
use std::borrow::Borrow;
use std::cell::{Cell, Ref, RefCell, UnsafeCell};
use std::collections::{HashMap};
use std::collections::linked_list::LinkedList;
use std::marker::PhantomData;
use std::mem;
use std::ops::Deref;
use std::ptr::{addr_of, NonNull};
use std::rc::Rc;
use std::sync::Arc;
use std::task::{RawWaker, RawWakerVTable, Wake, Waker};

//##################################################################################################//
/// Rc和Arc可以实现多所有权效果，通常用于想通过引用传递数据但是要避免复杂的生命周期控制，或者在线程之间传递变量
#[derive(Debug)]
struct RcModel {
    msg: String,
}

impl Drop for RcModel {
    fn drop(&mut self) {
        println!("Dropped!!")
    }
}

impl RcModel {
    pub fn new(msg: String) -> Self {
        Self { msg }
    }
}

#[test]
fn rc_test() {
    let rc = Rc::new(RcModel::new("asd".to_owned()));
    ///实现了Deref trait 可以直接吧如此当作RcModel使用
    println!("{:?}", rc);
    unsafe {
        // 可以通过直接获取内部指针实现对元素的操作
        let raw = Rc::into_raw(rc);
        unsafe_assign!(*raw, RcModel::new("asd".to_owned()));
        println!("{:?}", *raw);
        let _ = Rc::from_raw(raw);
    }
}

//##################################################################################################//
///UnsafeCell -> Cell -> RefCell
///cell提供一个基本的变量所有权的包装类型，提供内部访问，内部可替换，等功能, 其中get方法要求内部变量实现copy
///refcell提供一个可以通过引用方式修改内部变量的方式，refcell使用产生更小的开销

#[test]
fn cell_test() {
    let msg = "msg".to_string();
    let cell = Cell::new(msg);
    cell.set("暂时".to_string());

    println!("{:?}", cell.take());
}

#[test]
fn ref_cell_test() {
    let msg = "msg".to_string();
    let cell = RefCell::new(msg);
    *cell.borrow_mut() = "new".to_string();

    let mut list = LinkedList::new();
    list.push_front(1);
    println!("{:?}", list);
}